/*********************************************************************************
    This software is created under the term GNU General Public License.
    You should have received a copy of the GNU General Public License.
    If not, write to the Free Software Foundation, 59 Temple Place - Suite 330,
    Boston, MA 02111-1307, USA.

mem:
    rewrite a memory management. implement malloc, realloc and free.
    we use a global pool(heap *hp) for the source of memory. see the
    reference of heap

author: xiangyun.kong(lo-sor@hotmail.com)
create: 2-26-2011

changes:

**********************************************************************************/
#include <stdlib.h>

#include <assert.h>
#include <mem.h>
#include <critical.h>
#include "heap.h"

critical cs;
heap *hp = NULL;

void pool_init()
{
    if( hp == NULL )
    {
        init_critical( &cs );
        hp = hp_create( );
    }
}

void* pool_alloc( uint32 _size )
{
    void *mem = NULL;
    enter_critical( &cs );
    mem = hp_alloc( hp, _size );
    leave_critical( &cs );
    return mem;
}

void* pool_realloc( void *_ptr, uint32 _size )
{
    void *mem = NULL;
    uint32 org_size;

    if( _ptr == NULL )
        return pool_alloc( _size );

    enter_critical( &cs );
    org_size = hp_size( _ptr );
    if( _size == 0 )
        hp_free( hp, _ptr );
    else if( _size == org_size )
        mem = _ptr;
    else if( _size < org_size )
    {
        mem = hp_alloc( hp, _size );
        memcpy( mem, _ptr, _size );
        hp_free( hp, _ptr );
    }
    else
    {
        mem = hp_alloc( hp, _size );
        memcpy( mem, _ptr, org_size );
        hp_free( hp, _ptr );
    }
    leave_critical( &cs );
    return mem;
}

void pool_free( void* _ptr )
{
    enter_critical( &cs );
    hp_free( hp, _ptr );
    leave_critical( &cs );
}
